package com.chenqq.qsocket.fractory;

import com.chenqq.qsocket.configuration.MinaConfigInfo;
import com.chenqq.qsocket.message.SocketMessage;
import com.chenqq.qsocket.tools.HexDump;
import com.chenqq.qsocket.tools.LogShow;

import org.apache.mina.core.buffer.IoBuffer;
import org.apache.mina.core.session.IoSession;
import org.apache.mina.filter.codec.CumulativeProtocolDecoder;
import org.apache.mina.filter.codec.ProtocolDecoderOutput;

/**
 * 解码器TCP的
 */
public class TCPDecoder extends CumulativeProtocolDecoder {
    private IoBuffer buff = IoBuffer.allocate(200).setAutoExpand(true);

    @Override
    protected boolean doDecode(IoSession ioSession, IoBuffer ioBuffer, ProtocolDecoderOutput protocolDecoderOutput) throws Exception {
        int remaining = ioBuffer.remaining();
        LogShow.showE("接受信息"+remaining);
        if (remaining <= 2) {
            return false;
        }
        ioBuffer.mark();//标记方便下次回来
        byte[] header = new byte[2];
        ioBuffer.get(header);
        if (header[0] == SocketMessage.HEADER1 && header[1] == SocketMessage.HEADER2) {
            //头文件是我们要的协议文件
            byte b = ioBuffer.get();//类型
            LogShow.showE("解析类型"+b);
            if (ioBuffer.remaining() >= 2) {
                short bodyLength = ioBuffer.getShort();
                if (ioBuffer.remaining()<bodyLength){
                    ioBuffer.reset();
                    //数据长度不够
                    return false;
                }
                byte[] body=new byte[bodyLength];
                ioBuffer.get(body,0,body.length);
                SocketMessage msg = new SocketMessage();
                msg.setType(b);
                msg.setBody(body);
                protocolDecoderOutput.write(msg);
                if (ioBuffer.remaining() >= 2) {
                    return true;
                }
            }else {
                ioBuffer.reset();
            }
        } else {
            //按文字传递
            ioBuffer.reset();
            String hexDump = ioBuffer.getString(remaining, MinaConfigInfo.getInStance().getCharset()
            .newDecoder());
            protocolDecoderOutput.write(hexDump);
        }
        return false;
    }

    private void initIoBufeer(IoBuffer ioBuffer, ProtocolDecoderOutput protocolDecoderOutput) {
        while (ioBuffer.hasRemaining()) {
            // 判断消息是否是结束符，不同平台的结束符也不一样；
            // windows换行符（\r\n）就认为是一个完整消息的结束符了； UNIX 是\n；MAC 是\r
            byte b = ioBuffer.get();
            if (b == '\n') {
                buff.flip();
                byte[] bytes = new byte[buff.limit()];
                String s = guessEncoding(bytes);
                buff.get(bytes);
                String message = HexDump.toHexString(bytes);
                buff = IoBuffer.allocate(200).setAutoExpand(true);
                // 如果结束了，就写入转码后的数据
                protocolDecoderOutput.write(message);
            } else {
                buff.put(b);
            }
        }
    }


    public static String guessEncoding(byte[] bytes) {
        String DEFAULT_ENCODING = "UTF-8";

        org.mozilla.universalchardet.UniversalDetector detector =

                new org.mozilla.universalchardet.UniversalDetector(null);

        detector.handleData(bytes, 0, bytes.length);

        detector.dataEnd();

        String encoding = detector.getDetectedCharset();

        detector.reset();

        if (encoding == null) {
            encoding = DEFAULT_ENCODING;

        }
        return encoding;

    }
}
